interface Monitor{//显示器

}
interface Host{
    
}


class Container{
    private instances= new Map() //存放所有实例
    public properties= new Map() //存放所有属性
    bind(key:string,creater:()=>void){
        if(!this.instances.has(key)){
            this.instances.set(key,creater())
        }
    }
    resolve<T>(key:string):T{
        //将记录的属性，自动注入到当前的实例上
        const instances=this.instances.get(key)
        //解析依赖的属性
        for (const prop of this.properties) {
            const [key,ServiceKey]=prop;
            const [className,propName]=key.split('-')
            if(instances.constructor.name!==className){
                continue;
            }
            instances[propName]=this.resolve(ServiceKey)
        }
        
        return instances
    }
}
const container=new Container()
@Provide()
class  Monitor27inch implements Monitor{

}
@Provide()
class  AppleHost implements Host{
    
}

@Provide()
class  Monitor32inch implements Monitor{

}
@Provide()
class  HpHost implements Host{
    
}

@Provide()
class Computer{
    @Inject('Monitor32inch')
    monitor!:Monitor32inch
    @Inject('HpHost')
    host!:HpHost
    boostrap(){
        console.log('启动电脑',this);
        
    }

}

function Provide(key?:string){
    return (target:any)=>{
        container.bind(target.name,()=>new target())
    }
}

function Inject(injectKey:string){
    return (target:object,key:string)=>{
        //当前在那个原型上，注入了那些属性，做一个映射关系，稍后解析电脑的时候自己解析他所依赖的属性
        container.properties.set(`${target.constructor.name}-${key}`,injectKey)
    }
}
const computer=container.resolve<Computer>('Computer')
computer.boostrap()
console.log(1000,computer);
